#include "OgreVM.h"
#include "DIVA_Manager.h"
long int OgreVM::num = 0;

OgreVM::OgreVM(){
	_mgr = DIVA_Manager::getInstance()->getSceneManager();
	OgreVM::num ++;
	_VMName = "DIVA_VM_"+Ogre::StringConverter::toString(OgreVM::num);	
	_ParentSceneNode = _mgr->getRootSceneNode();
	_SceneNode = _ParentSceneNode->createChildSceneNode(_VMName);
	entityNum = 0;
}


OgreVM::~OgreVM(){
    _VMName = Ogre::StringUtil::BLANK;
	_SceneNode->removeAndDestroyAllChildren();
	//will they delete Entity?
	
}
std::string OgreVM::getSceneNodeName() { return _VMName ; }
std::string OgreVM::getNewUniqueName(){

	std::string name = _VMName;
	return name;
}
std::string OgreVM::getNewUniqueName(std::string specialhead){
	std::string name = (specialhead+"_"+Ogre::StringConverter::toString(entityNum++));
	return name;
}
void OgreVM::setPosition(Ogre::Vector3 pos){
	assert(_ParentSceneNode != NULL);
	_SceneNode->setPosition(pos);	
	position = pos ;
}

void OgreVM::setSceneNodeScale(Ogre::Vector3 size){
	_SceneNode->setScale(size);
}
Ogre::Vector3 OgreVM::getSceneNodeScale(){
	return _SceneNode->getScale();
}


void OgreVM::roll(Ogre::Real Degree){
	if (_ParentSceneNode == _mgr->getRootSceneNode())//不是group
		_SceneNode->roll(Ogre::Degree(Degree));
	else//group strong attach
		_ParentSceneNode->roll(Ogre::Degree(Degree));
}

void OgreVM::showBoundingBox(bool show){
	_SceneNode->showBoundingBox(show);	
}
Ogre::Vector3 OgreVM::getPosition(){
	return _SceneNode->getPosition();
}
Ogre::Vector3 OgreVM::getWorldPosition() {
	return _SceneNode->_getDerivedPosition();
}
/*
Vector3 OgreVM::getBasicSize(){
	short n = _SceneNode->numAttachedObjects();
	Vector3 max = Vector3(0,0,0);
	for(int i= 0; i < n; i++){
		Ogre::MovableObject* e = _SceneNode->getAttachedObject(i);
		AxisAlignedBox temp = e->getBoundingBox();	
		Vector3 size = temp.getSize();
		if(size.x > max.x)
			max.x = size.x;
		if(size.y > max.y)
			max.y = size.y;
		if(size.z > max.z)
			max.z = size.z;
	}
	return max;
}
*/

/*
Vector3 OgreVM::getActualSize(){
	return getOriginalBodySize()*getSceneNodeScale();
}
*/

void OgreVM::scaleSceneNodeToAbsSize(Ogre::Vector3 v) {
	Ogre::Vector3 def = getOriginalBodySize();
	setSceneNodeScale(Ogre::Vector3(v.x/def.x,v.y/def.y,v.z/def.z));
}
void OgreVM::scaleBodyToAbsSize(Ogre::Vector3 v){
	Ogre::Vector3 def = getOriginalBodySize();

	//避免除數為0導致錯誤
	if ( def.x==0 || def.y==0 || def.z==0 ){
		return;
	}
	setBodyScale(Ogre::Vector3(v.x/def.x,v.y/def.y,v.z/def.z));
}

Ogre::SceneNode* OgreVM::getParentSceneNode(void){
	return _ParentSceneNode;
}

Ogre::SceneNode *OgreVM::getSceneNode(void){
	return _SceneNode;
}


void OgreVM::setParentSceneNode(Ogre::SceneNode* s){
	_ParentSceneNode = s; 
}

/*
void OgreVM::setSceneNode(SceneNode* s){
	_SceneNode = s;
}
*/
Ogre::Vector3 OgreVM::getNewPosition() {
	Ogre::Vector3 newpos ;
	int modnum ;
	Ogre::Real length ;

	length = (num/16+1) * 30 ;
	modnum = num % 16 ;
	newpos.x = length * Ogre::Math::Cos(Ogre::Math::TWO_PI *(40-modnum*5)/360) ;
	newpos.y = length * Ogre::Math::Sin(Ogre::Math::TWO_PI *(40-modnum*5)/360);
	newpos.z = length * Ogre::Math::Tan(Ogre::Math::TWO_PI *(40-modnum*5)/360) ;
	return newpos ;
}

void OgreVM::rotate(Ogre::Vector3 rotateTo){
	// please read http://www.ogre3d.org/wiki/index.php/Quaternion_and_Rotation_Primer
	// for further details about rotate

	Ogre::Vector3 direction=_SceneNode->getOrientation()*Ogre::Vector3::UNIT_Z;
	rotateTo=direction+rotateTo.normalisedCopy();
	Ogre::Quaternion rotate=direction.getRotationTo(rotateTo.normalisedCopy());
	_SceneNode->rotate(rotate);

}

void OgreVM::rotate(Ogre::Real x, Ogre::Real y, Ogre::Real z){
	
	this->rotate(Ogre::Vector3(x,y,z));

}